home *** CD-ROM | disk | FTP | other *** search
/ CU Amiga Super CD-ROM 14 / CU Amiga Magazine's Super CD-ROM 14 (1997)(EMAP Images)(GB)(Track 1 of 3)[!][issue 1997-09].iso / CUCD / Programming / Mesa-2.2 / src-glu / nurbs.c < prev    next >
Encoding:
C/C++ Source or Header  |  1996-09-27  |  15.4 KB  |  632 lines

  1. /* $Id: nurbs.c,v 1.2 1996/09/27 23:11:23 brianp Exp $ */
  2.  
  3. /*
  4.  * Mesa 3-D graphics library
  5.  * Version:  2.0
  6.  * Copyright (C) 1995-1996  Brian Paul
  7.  *
  8.  * This library is free software; you can redistribute it and/or
  9.  * modify it under the terms of the GNU Library General Public
  10.  * License as published by the Free Software Foundation; either
  11.  * version 2 of the License, or (at your option) any later version.
  12.  *
  13.  * This library is distributed in the hope that it will be useful,
  14.  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  15.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  16.  * Library General Public License for more details.
  17.  *
  18.  * You should have received a copy of the GNU Library General Public
  19.  * License along with this library; if not, write to the Free
  20.  * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  21.  */
  22.  
  23.  
  24. /*
  25.  * $Log: nurbs.c,v $
  26.  * Revision 1.2  1996/09/27 23:11:23  brianp
  27.  * ifdef'd out unimplemented trimmed nurbs code
  28.  *
  29.  * Revision 1.1  1996/09/27 01:19:39  brianp
  30.  * Initial revision
  31.  *
  32.  */
  33.  
  34.  
  35. /*
  36.  * NURBS implementation written by Bogdan Sikorski (bogdan@cira.it)
  37.  * See README2 for more info.
  38.  */
  39.  
  40.  
  41. #include <math.h>
  42. #include <stdio.h>
  43. #include <stdlib.h>
  44. #include "nurbs.h"
  45.  
  46.  
  47. void
  48. call_user_error( GLUnurbsObj *nobj, GLenum error )
  49. {
  50.     nobj->error=error;
  51.     if(nobj->error_callback != NULL) {
  52.         (*(nobj->error_callback))(error);
  53.     }
  54.     else {
  55.        printf("NURBS error %d %s\n", error, gluErrorString(error) );
  56.     }
  57. }
  58.  
  59.  
  60.  
  61. GLUnurbsObj *gluNewNurbsRenderer( void )
  62. {
  63.    GLUnurbsObj *n;
  64.    GLfloat tmp_viewport[4];
  65.    GLint i,j;
  66.  
  67.    n = (GLUnurbsObj *) malloc( sizeof(GLUnurbsObj) );
  68.    if (n) {
  69.       /* init */
  70.       n->culling=GL_FALSE;
  71.       n->nurbs_type=GLU_NURBS_NONE;
  72.       n->error=GLU_NO_ERROR;
  73.       n->error_callback=NULL;
  74.       n->auto_load_matrix=GL_TRUE;
  75.       n->sampling_tolerance=50.0;
  76.       n->display_mode=GLU_FILL;
  77.       /* in case the user doesn't supply the sampling matrices */
  78.       /* set projection and modelview to identity */
  79.       for(i=0;i<4;i++)
  80.           for(j=0;j<4;j++)
  81.               if(i==j)
  82.               {
  83.                 n->sampling_matrices.model[i*4+j]=1.0;
  84.                 n->sampling_matrices.proj[i*4+j]=1.0;
  85.             }
  86.             else
  87.               {
  88.                 n->sampling_matrices.model[i*4+j]=0.0;
  89.                 n->sampling_matrices.proj[i*4+j]=0.0;
  90.             }
  91.       /* and set the viewport sampling matrix to current ciewport */
  92.       glGetFloatv(GL_VIEWPORT,tmp_viewport);
  93.       for(i=0;i<4;i++)
  94.           n->sampling_matrices.viewport[i]=tmp_viewport[i];
  95.       n->trim=NULL;
  96.    }
  97.    return n;
  98. }
  99.  
  100.  
  101.  
  102. void gluDeleteNurbsRenderer( GLUnurbsObj *nobj )
  103. {
  104.    if (nobj) {
  105.       free( nobj );
  106.    }
  107. }
  108.  
  109.  
  110.  
  111. void gluLoadSamplingMatrices( GLUnurbsObj *nobj,
  112.                   const GLfloat modelMatrix[16],
  113.                   const GLfloat projMatrix[16],
  114.                   const GLint viewport[4] )
  115. {
  116.     GLint    i;
  117.  
  118.     for(i=0;i<16;i++)
  119.     {
  120.         nobj->sampling_matrices.model[i]=modelMatrix[i];
  121.         nobj->sampling_matrices.proj[i]=projMatrix[i];
  122.     }
  123.     for(i=0;i<4;i++)
  124.         nobj->sampling_matrices.viewport[i]=viewport[i];
  125. }
  126.  
  127.  
  128. void gluNurbsProperty( GLUnurbsObj *nobj, GLenum property, GLfloat value )
  129. {
  130.    GLenum val;
  131.  
  132.    switch (property) {
  133.       case GLU_SAMPLING_TOLERANCE:
  134.            if(value <= 0.0)
  135.            {
  136.                call_user_error(nobj,GLU_INVALID_VALUE);
  137.                return;
  138.          }
  139.          nobj->sampling_tolerance=value;
  140.          break;
  141.       case GLU_DISPLAY_MODE:
  142.          val=(GLenum)value;
  143.          if(val!=GLU_FILL && val!=GLU_OUTLINE_POLYGON && val!=GLU_OUTLINE_PATCH)
  144.          {
  145.              call_user_error(nobj,GLU_INVALID_ENUM);
  146.              return;
  147.          }
  148.          if(nobj->nurbs_type==GLU_NURBS_CURVE)
  149.          {
  150.              call_user_error(nobj,GLU_NURBS_ERROR26);
  151.              return;
  152.          }
  153.          nobj->display_mode=val;
  154. if(val==GLU_OUTLINE_PATCH)
  155.     fprintf(stderr,"NURBS, for the moment, can display only in POLYGON mode\n");
  156.          break;
  157.       case GLU_CULLING:
  158.          val=(GLenum)value;
  159.          if(val!=GL_TRUE && val!=GL_FALSE)
  160.          {
  161.              call_user_error(nobj,GLU_INVALID_ENUM);
  162.              return;
  163.          }
  164.          nobj->culling = (GLboolean) value;
  165.          break;
  166.       case GLU_AUTO_LOAD_MATRIX:
  167.          val=(GLenum)value;
  168.          if(val!=GL_TRUE && val!=GL_FALSE)
  169.          {
  170.              call_user_error(nobj,GLU_INVALID_ENUM);
  171.              return;
  172.          }
  173.          nobj->auto_load_matrix = (GLboolean) value;
  174.          break;
  175.       default:
  176.          call_user_error(nobj,GLU_NURBS_ERROR26);
  177.    }
  178. }
  179.  
  180.  
  181. void gluGetNurbsProperty( GLUnurbsObj *nobj, GLenum property, GLfloat *value )
  182. {
  183.    switch (property) {
  184.       case GLU_SAMPLING_TOLERANCE:
  185.          *value = nobj->sampling_tolerance;
  186.          break;
  187.       case GLU_DISPLAY_MODE:
  188.          *value = (GLfloat) nobj->display_mode;
  189.          break;
  190.       case GLU_CULLING:
  191.      *value = nobj->culling ? 1.0 : 0.0;
  192.          break;
  193.       case GLU_AUTO_LOAD_MATRIX:
  194.          *value = nobj->auto_load_matrix ? 1.0 : 0.0;
  195.      break;
  196.       default:
  197.          call_user_error(nobj,GLU_INVALID_ENUM);
  198.    }
  199. }
  200.  
  201.  
  202.  
  203. void gluBeginCurve( GLUnurbsObj *nobj )
  204. {
  205.     if(nobj->nurbs_type==GLU_NURBS_CURVE)
  206.     {
  207.         call_user_error(nobj,GLU_NURBS_ERROR6);
  208.         return;
  209.     }
  210.     nobj->nurbs_type=GLU_NURBS_CURVE;
  211.     nobj->curve.geom.type=GLU_INVALID_ENUM;
  212.     nobj->curve.color.type=GLU_INVALID_ENUM;
  213.     nobj->curve.texture.type=GLU_INVALID_ENUM;
  214.     nobj->curve.normal.type=GLU_INVALID_ENUM;
  215. }
  216.  
  217.  
  218. void gluEndCurve( GLUnurbsObj * nobj )
  219. {
  220.     if(nobj->nurbs_type==GLU_NURBS_NONE)
  221.     {
  222.         call_user_error(nobj,GLU_NURBS_ERROR7);
  223.         return;
  224.     }
  225.     if(nobj->curve.geom.type==GLU_INVALID_ENUM)
  226.     {
  227.         call_user_error(nobj,GLU_NURBS_ERROR8);
  228.         nobj->nurbs_type=GLU_NURBS_NONE;
  229.         return;
  230.     }
  231.     glPushAttrib( (GLbitfield) (GL_EVAL_BIT | GL_ENABLE_BIT) );
  232.     glDisable(GL_MAP1_VERTEX_3);
  233.     glDisable(GL_MAP1_VERTEX_4);
  234.     glDisable(GL_MAP1_INDEX);
  235.     glDisable(GL_MAP1_COLOR_4);
  236.     glDisable(GL_MAP1_NORMAL);
  237.     glDisable(GL_MAP1_TEXTURE_COORD_1);
  238.     glDisable(GL_MAP1_TEXTURE_COORD_2);
  239.     glDisable(GL_MAP1_TEXTURE_COORD_3);
  240.     glDisable(GL_MAP1_TEXTURE_COORD_4);
  241.     glDisable(GL_MAP2_VERTEX_3);
  242.     glDisable(GL_MAP2_VERTEX_4);
  243.     glDisable(GL_MAP2_INDEX);
  244.     glDisable(GL_MAP2_COLOR_4);
  245.     glDisable(GL_MAP2_NORMAL);
  246.     glDisable(GL_MAP2_TEXTURE_COORD_1);
  247.     glDisable(GL_MAP2_TEXTURE_COORD_2);
  248.     glDisable(GL_MAP2_TEXTURE_COORD_3);
  249.     glDisable(GL_MAP2_TEXTURE_COORD_4);
  250.     do_nurbs_curve(nobj);
  251.     glPopAttrib();
  252.     nobj->nurbs_type=GLU_NURBS_NONE;
  253. }
  254.  
  255.  
  256. void gluNurbsCurve( GLUnurbsObj *nobj, GLint nknots, GLfloat *knot,
  257.             GLint stride, GLfloat *ctlarray, GLint order, GLenum type )
  258. {
  259.     if(nobj->nurbs_type==GLU_NURBS_TRIM)
  260.     {
  261. #if 0
  262. /* TODO: NOT IMPLEMENTED YET */
  263.         nurbs_trim *ptr1;
  264.         trim_list *ptr2;
  265.  
  266.         if(type!=GLU_MAP1_TRIM_2 && type!=GLU_MAP1_TRIM_3)
  267.         {
  268.             call_user_error(nobj,GLU_NURBS_ERROR14);
  269.             return;
  270.         }
  271.         for(ptr1=nobj->trim;ptr1->next;ptr1=ptr1->next);
  272.         if(ptr1->trim_loop)
  273.         {
  274.             for(ptr2=ptr1->trim_loop;ptr2->next;ptr2=ptr2->next);
  275.             if((ptr2->next=(trim_list *)malloc(sizeof(trim_list)))==NULL)
  276.             {
  277.                 call_user_error(nobj,GLU_OUT_OF_MEMORY);
  278.                 return;
  279.             }
  280.             ptr2=ptr2->next;
  281.         }
  282.         else
  283.         {
  284.             if((ptr2=(trim_list *)malloc(sizeof(trim_list)))==NULL)
  285.             {
  286.                 call_user_error(nobj,GLU_OUT_OF_MEMORY);
  287.                 return;
  288.             }
  289.             ptr1->trim_loop=ptr2;
  290.         }
  291.         ptr2->trim_type=GLU_TRIM_NURBS;
  292.         ptr2->curve.nurbs_curve.knot_count=nknots;
  293.         ptr2->curve.nurbs_curve.knot=knot;
  294.         ptr2->curve.nurbs_curve.stride=stride;
  295.         ptr2->curve.nurbs_curve.ctrlarray=ctlarray;
  296.         ptr2->curve.nurbs_curve.order=order;
  297.         ptr2->curve.nurbs_curve.dim= (type==GLU_MAP1_TRIM_2 ? 2 : 3 );
  298.         ptr2->curve.nurbs_curve.type=type;
  299.         ptr2->next=NULL;
  300. #endif
  301.     }
  302.     else
  303.     {
  304.         if(type==GLU_MAP1_TRIM_2 || type==GLU_MAP1_TRIM_3)
  305.         {
  306.             call_user_error(nobj,GLU_NURBS_ERROR22);
  307.             return;
  308.         }
  309.         if(nobj->nurbs_type!=GLU_NURBS_CURVE)
  310.         {
  311.             call_user_error(nobj,GLU_NURBS_ERROR10);
  312.             return;
  313.         }
  314.         switch(type)
  315.         {
  316.             case GL_MAP1_VERTEX_3:
  317.             case GL_MAP1_VERTEX_4:
  318.                 if(nobj->curve.geom.type!=GLU_INVALID_ENUM)
  319.                 {
  320.                     call_user_error(nobj,GLU_NURBS_ERROR8);
  321.                     return;
  322.                 }
  323.                 nobj->curve.geom.type=type;
  324.                 nobj->curve.geom.knot_count=nknots;
  325.                 nobj->curve.geom.knot=knot;
  326.                 nobj->curve.geom.stride=stride;
  327.                 nobj->curve.geom.ctrlarray=ctlarray;
  328.                 nobj->curve.geom.order=order;
  329.                 break;
  330.             case GL_MAP1_INDEX:
  331.             case GL_MAP1_COLOR_4:
  332.                 nobj->curve.color.type=type;
  333.                 nobj->curve.color.knot_count=nknots;
  334.                 nobj->curve.color.knot=knot;
  335.                 nobj->curve.color.stride=stride;
  336.                 nobj->curve.color.ctrlarray=ctlarray;
  337.                 nobj->curve.color.order=order;
  338.                 break;
  339.             case GL_MAP1_NORMAL:
  340.                 nobj->curve.normal.type=type;
  341.                 nobj->curve.normal.knot_count=nknots;
  342.                 nobj->curve.normal.knot=knot;
  343.                 nobj->curve.normal.stride=stride;
  344.                 nobj->curve.normal.ctrlarray=ctlarray;
  345.                 nobj->curve.normal.order=order;
  346.                 break;
  347.             case GL_MAP1_TEXTURE_COORD_1:
  348.             case GL_MAP1_TEXTURE_COORD_2:
  349.             case GL_MAP1_TEXTURE_COORD_3:
  350.             case GL_MAP1_TEXTURE_COORD_4:
  351.                 nobj->curve.texture.type=type;
  352.                 nobj->curve.texture.knot_count=nknots;
  353.                 nobj->curve.texture.knot=knot;
  354.                 nobj->curve.texture.stride=stride;
  355.                 nobj->curve.texture.ctrlarray=ctlarray;
  356.                 nobj->curve.texture.order=order;
  357.                 break;
  358.             default:
  359.                  call_user_error(nobj,GLU_INVALID_ENUM);
  360.         }
  361.     }
  362. }
  363.  
  364.  
  365. void gluBeginSurface( GLUnurbsObj *nobj )
  366. {
  367.     switch(nobj->nurbs_type)
  368.     {
  369.         case GLU_NURBS_NONE:
  370.             nobj->nurbs_type=GLU_NURBS_SURFACE;
  371.             nobj->surface.geom.type=GLU_INVALID_ENUM;
  372.             nobj->surface.color.type=GLU_INVALID_ENUM;
  373.             nobj->surface.texture.type=GLU_INVALID_ENUM;
  374.             nobj->surface.normal.type=GLU_INVALID_ENUM;
  375.             break;
  376.         case GLU_NURBS_TRIM:
  377.             call_user_error(nobj,GLU_NURBS_ERROR16);
  378.             break;
  379.         case GLU_NURBS_SURFACE:
  380.         case GLU_NURBS_NO_TRIM:
  381.         case GLU_NURBS_TRIM_DONE:
  382.             call_user_error(nobj,GLU_NURBS_ERROR27);
  383.             break;
  384.         case GLU_NURBS_CURVE:
  385.             call_user_error(nobj,GLU_NURBS_ERROR6);
  386.             break;
  387.     }
  388. }
  389.  
  390.  
  391. void gluEndSurface( GLUnurbsObj * nobj )
  392. {
  393.     switch(nobj->nurbs_type)
  394.     {
  395.         case GLU_NURBS_NONE:
  396.             call_user_error(nobj,GLU_NURBS_ERROR13);
  397.             break;
  398.         case GLU_NURBS_TRIM:
  399.             call_user_error(nobj,GLU_NURBS_ERROR12);
  400.             break;
  401.         case GLU_NURBS_TRIM_DONE:
  402. /*            if(nobj->trim->trim_loop==NULL)
  403.             {
  404.                 call_user_error(nobj,GLU_NURBS_ERROR18);
  405.                 return;
  406.             }*/
  407.             /* no break - fallthrough */
  408.         case GLU_NURBS_NO_TRIM:
  409.             glPushAttrib( (GLbitfield) (GL_EVAL_BIT | GL_ENABLE_BIT) );
  410.             glDisable(GL_MAP2_VERTEX_3);
  411.             glDisable(GL_MAP2_VERTEX_4);
  412.             glDisable(GL_MAP2_INDEX);
  413.             glDisable(GL_MAP2_COLOR_4);
  414.             glDisable(GL_MAP2_NORMAL);
  415.             glDisable(GL_MAP2_TEXTURE_COORD_1);
  416.             glDisable(GL_MAP2_TEXTURE_COORD_2);
  417.             glDisable(GL_MAP2_TEXTURE_COORD_3);
  418.             glDisable(GL_MAP2_TEXTURE_COORD_4);
  419. /*            glDisable(GL_MAP1_VERTEX_3);
  420.             glDisable(GL_MAP1_VERTEX_4);
  421.             glDisable(GL_MAP1_INDEX);
  422.             glDisable(GL_MAP1_COLOR_4);
  423.             glDisable(GL_MAP1_NORMAL);
  424.             glDisable(GL_MAP1_TEXTURE_COORD_1);
  425.             glDisable(GL_MAP1_TEXTURE_COORD_2);
  426.             glDisable(GL_MAP1_TEXTURE_COORD_3);
  427.             glDisable(GL_MAP1_TEXTURE_COORD_4);*/
  428.             do_nurbs_surface(nobj);
  429.             glPopAttrib();
  430.             break;
  431.         default:
  432.             call_user_error(nobj,GLU_NURBS_ERROR8);
  433.     }
  434.     nobj->nurbs_type=GLU_NURBS_NONE;
  435. }
  436.  
  437.  
  438. void gluNurbsSurface( GLUnurbsObj *nobj,
  439.               GLint sknot_count, GLfloat *sknot,
  440.               GLint tknot_count, GLfloat *tknot,
  441.               GLint s_stride, GLint t_stride,
  442.               GLfloat *ctrlarray,
  443.               GLint sorder, GLint torder,
  444.               GLenum type )
  445. {
  446.     if(nobj->nurbs_type==GLU_NURBS_NO_TRIM || nobj->nurbs_type==GLU_NURBS_TRIM ||
  447.         nobj->nurbs_type==GLU_NURBS_TRIM_DONE)
  448.     {
  449.         if(type==GL_MAP2_VERTEX_3 || type==GL_MAP2_VERTEX_4)
  450.         {
  451.             call_user_error(nobj,GLU_NURBS_ERROR8);
  452.             return;
  453.         }
  454.     }
  455.     else
  456.     if(nobj->nurbs_type!=GLU_NURBS_SURFACE)
  457.     {
  458.         call_user_error(nobj,GLU_NURBS_ERROR11);
  459.         return;
  460.     }
  461.     switch(type)
  462.     {
  463.         case GL_MAP2_VERTEX_3:
  464.         case GL_MAP2_VERTEX_4:
  465.             nobj->surface.geom.sknot_count=sknot_count;
  466.             nobj->surface.geom.sknot=sknot;
  467.             nobj->surface.geom.tknot_count=tknot_count;
  468.             nobj->surface.geom.tknot=tknot;
  469.             nobj->surface.geom.s_stride=s_stride;
  470.             nobj->surface.geom.t_stride=t_stride;
  471.             nobj->surface.geom.ctrlarray=ctrlarray;
  472.             nobj->surface.geom.sorder=sorder;
  473.             nobj->surface.geom.torder=torder;
  474.             nobj->surface.geom.type=type;
  475.             nobj->nurbs_type=GLU_NURBS_NO_TRIM;
  476.             break;
  477.         case GL_MAP2_INDEX:
  478.         case GL_MAP2_COLOR_4:
  479.             nobj->surface.color.sknot_count=sknot_count;
  480.             nobj->surface.color.sknot=sknot;
  481.             nobj->surface.color.tknot_count=tknot_count;
  482.             nobj->surface.color.tknot=tknot;
  483.             nobj->surface.color.s_stride=s_stride;
  484.             nobj->surface.color.t_stride=t_stride;
  485.             nobj->surface.color.ctrlarray=ctrlarray;
  486.             nobj->surface.color.sorder=sorder;
  487.             nobj->surface.color.torder=torder;
  488.             nobj->surface.color.type=type;
  489.             break;
  490.         case GL_MAP2_NORMAL:
  491.             nobj->surface.normal.sknot_count=sknot_count;
  492.             nobj->surface.normal.sknot=sknot;
  493.             nobj->surface.normal.tknot_count=tknot_count;
  494.             nobj->surface.normal.tknot=tknot;
  495.             nobj->surface.normal.s_stride=s_stride;
  496.             nobj->surface.normal.t_stride=t_stride;
  497.             nobj->surface.normal.ctrlarray=ctrlarray;
  498.             nobj->surface.normal.sorder=sorder;
  499.             nobj->surface.normal.torder=torder;
  500.             nobj->surface.normal.type=type;
  501.             break;
  502.         case GL_MAP2_TEXTURE_COORD_1:
  503.         case GL_MAP2_TEXTURE_COORD_2:
  504.         case GL_MAP2_TEXTURE_COORD_3:
  505.         case GL_MAP2_TEXTURE_COORD_4:
  506.             nobj->surface.texture.sknot_count=sknot_count;
  507.             nobj->surface.texture.sknot=sknot;
  508.             nobj->surface.texture.tknot_count=tknot_count;
  509.             nobj->surface.texture.tknot=tknot;
  510.             nobj->surface.texture.s_stride=s_stride;
  511.             nobj->surface.texture.t_stride=t_stride;
  512.             nobj->surface.texture.ctrlarray=ctrlarray;
  513.             nobj->surface.texture.sorder=sorder;
  514.             nobj->surface.texture.torder=torder;
  515.             nobj->surface.texture.type=type;
  516.             break;
  517.         default:
  518.              call_user_error(nobj,GLU_INVALID_ENUM);
  519.     }
  520. }
  521.  
  522.  
  523. void
  524. gluNurbsCallback( GLUnurbsObj *nobj, GLenum which, void (*fn)(GLenum))
  525. {
  526.     nobj->error_callback=fn;
  527.     if(which!=GLU_ERROR)
  528.         call_user_error(nobj,GLU_INVALID_ENUM);
  529. }
  530.  
  531. void
  532. gluBeginTrim( GLUnurbsObj *nobj )
  533. {
  534. #if 0
  535.     nurbs_trim *ptr;
  536. #endif
  537.  
  538.     if(nobj->nurbs_type!=GLU_NURBS_TRIM_DONE)
  539.         if(nobj->nurbs_type!=GLU_NURBS_NO_TRIM)
  540.         {
  541.             call_user_error(nobj,GLU_NURBS_ERROR15);
  542.             return;
  543.         }
  544.     nobj->nurbs_type=GLU_NURBS_TRIM;
  545. fprintf(stderr,"NURBS - trimming not supported yet\n");
  546. #if 0
  547.     if((ptr=(nurbs_trim *)malloc(sizeof(nurbs_trim)))==NULL)
  548.     {
  549.         call_user_error(nobj,GLU_OUT_OF_MEMORY);
  550.         return;
  551.     }
  552.     if(nobj->trim)
  553.     {
  554.         nurbs_trim *tmp_ptr;
  555.  
  556.         for(tmp_ptr=nobj->trim;tmp_ptr->next;tmp_ptr=tmp_ptr->next);
  557.         tmp_ptr->next=ptr;
  558.     }
  559.     else
  560.         nobj->trim=ptr;
  561.     ptr->trim_loop=NULL;
  562.     ptr->segments=NULL;
  563.     ptr->next=NULL;
  564. #endif
  565. }
  566.  
  567. void
  568. gluPwlCurve( GLUnurbsObj *nobj, GLint count, GLfloat *array, GLint stride,
  569.     GLenum type)
  570. {
  571. #if 0
  572.     nurbs_trim *ptr1;
  573.     trim_list *ptr2;
  574. #endif
  575.     if(nobj->nurbs_type==GLU_NURBS_CURVE)
  576.     {
  577.         call_user_error(nobj,GLU_NURBS_ERROR9);
  578.         return;
  579.     }
  580.     if(nobj->nurbs_type==GLU_NURBS_NONE)
  581.     {
  582.         call_user_error(nobj,GLU_NURBS_ERROR19);
  583.         return;
  584.     }
  585.     if(type!=GLU_MAP1_TRIM_2 && type!=GLU_MAP1_TRIM_3)
  586.     {
  587.         call_user_error(nobj,GLU_NURBS_ERROR14);
  588.         return;
  589.     }
  590. #if 0
  591.     for(ptr1=nobj->trim;ptr1->next;ptr1=ptr1->next);
  592.     if(ptr1->trim_loop)
  593.     {
  594.         for(ptr2=ptr1->trim_loop;ptr2->next;ptr2=ptr2->next);
  595.         if((ptr2->next=(trim_list *)malloc(sizeof(trim_list)))==NULL)
  596.         {
  597.             call_user_error(nobj,GLU_OUT_OF_MEMORY);
  598.             return;
  599.         }
  600.         ptr2=ptr2->next;
  601.     }
  602.     else
  603.     {
  604.         if((ptr2=(trim_list *)malloc(sizeof(trim_list)))==NULL)
  605.         {
  606.             call_user_error(nobj,GLU_OUT_OF_MEMORY);
  607.             return;
  608.         }
  609.         ptr1->trim_loop=ptr2;
  610.     }
  611.     ptr2->trim_type=GLU_TRIM_PWL;
  612.     ptr2->curve.pwl_curve.pt_count=count;
  613.     ptr2->curve.pwl_curve.ctrlarray=array;
  614.     ptr2->curve.pwl_curve.stride=stride;
  615.     ptr2->curve.pwl_curve.dim= (type==GLU_MAP1_TRIM_2 ? 2 : 3 );
  616.     ptr2->curve.pwl_curve.type=type;
  617.     ptr2->next=NULL;
  618. #endif
  619. }
  620.  
  621. void
  622. gluEndTrim( GLUnurbsObj *nobj )
  623. {
  624.     if(nobj->nurbs_type!=GLU_NURBS_TRIM)
  625.     {
  626.         call_user_error(nobj,GLU_NURBS_ERROR17);
  627.         return;
  628.     }
  629.     nobj->nurbs_type=GLU_NURBS_TRIM_DONE;
  630. }
  631.  
  632.